<template>
  <div>
    <el-table :data="renderDynamic" ref="multipleTable" border row-key="key" :row-class-name="rowClassNameFun"
              :header-row-class-name="headerRowClassName" size="mini" max-height="500px" style="width: 100%"
              @select="selectFun" @select-all="selectAllFun" :header-cell-style="{ background: '#fafafa' }"
              @selection-change="handleSelectionChange" @expand-change="expandChange"
    >
      <el-table-column type="selection" width="55" :selectable="checkFeeSelectable"></el-table-column>
      <el-table-column prop="name" label="费用名称" width="180">
      </el-table-column>
      <el-table-column prop="itemSum" label="金额" width="180">
        <template slot-scope="scope">
          <div
            v-if="['houseChargeItem', 'cashPledgeChargeItem'].includes(scope.row.key)|| ['houseChargeItem', 'cashPledgeChargeItem'].includes(scope.row.parentKey)"
          >{{ scope.row.itemSum }}
          </div>
          <div v-else>-{{ scope.row.itemSum }}</div>
        </template>
      </el-table-column>
      <el-table-column prop="address" label="操作">
        <template slot-scope="scope">
          <div v-if="scope.row.children &&scope.row.children.length>0">
            <el-button type="text" v-if="!scope.row.isExpand" @click="expand(scope.row)">展开明细</el-button>
            <el-button type="text" v-else @click="expand(scope.row)">收起明细</el-button>
          </div>

        </template>
      </el-table-column>
    </el-table>
  </div>
</template>

<script>
import { debounce } from '@/utils'

export default {
  name: 'PriceTable',
  props: {
    data: {
      default: {}
    },
    remainingSum: {
      default: 0
    },
    isCancal: {
      default: false
    },
    selection: {
      default: []
    },
    isDetail: {
      default: false
    }
  },
  data() {
    return {
      renderDynamic: [],
      orderInfo: {},
      feeObj: {
        'houseChargeItem': '房费',
        'cashPledgeChargeItem': '押金',
        'unsubscribeRefundItem': '退订费',
        'houseRefundItem': '已住房费',
        'facilityRefundItem': '损坏赔偿',
        'checkOutDelayRefundItem': '延迟退房费',
        'serviceCharge':'违约费'
      }
    }
  },
  created() {
    this.orderInfo = this.data
    let feeObj = this.orderInfo.order.orderPriceVO
    if (feeObj) {
      let data = []
      for (const key in feeObj) {
        if (Object.hasOwnProperty.call(feeObj, key)) {
          if (feeObj[key]) {
            feeObj[key]['parentKey'] = 0
            let obj = this.detailList(key, feeObj[key])
            data.push(obj)
          }

        }
      }
      this.renderDynamic = data
      console.log('data', data)
      this.toggleSelection(data, 1)
    } else {
      this.renderDynamic = []
    }

  },
  mounted() {
    if(this.isDetail){
      this.$nextTick(() => {
        let orderRefundDetailsList = this.orderInfo.orderRefundDetailsList
        let unsubscribeRefundList = this.renderDynamic.find(item => item.key == 'unsubscribeRefundItem')
        if (unsubscribeRefundList && unsubscribeRefundList.children) {
          // let list = unsubscribeRefundList.children.filter(item => {
          //   let obj = orderRefundDetailsList.find(oitem => oitem.id == item.id)
          //   if (obj && obj.refundState === '0') {
          //     return item
          //   }
          // })
          // console.log('list', list)
          // //勾选复选框
          // this.toggleSelection(list, true)

          let list = unsubscribeRefundList.children.map(item => {
            let obj = orderRefundDetailsList.find(oitem => oitem.id == item.id)
            item['openRenderSelect'] = true
            if (obj && obj.refundState === '0') {
              item['renderSelect'] = true
            } else {
              item['renderSelect'] = false
            }
            return item
          })
          console.log('list', list)
          //勾选复选框
          this.toggleSelection(list)
        }

      })
    }

  },
  methods: {
    // 勾选/取消全选 回调函数
    toggleSelection(rows) {
      this.$nextTick(() => {
        if (rows) {
          rows.forEach(row => {
            // this.$refs.multipleTable.toggleRowSelection(row)
            this.setRowIsSelect(row)
          })
        }
      })
    }
    ,
    // 检查是否可勾选
    checkFeeSelectable(row) {
      if (!this.isCancal || this.isDetail) return false
      if (row.fixedSelect) {
        return false
      }
      return true
    }
    ,
    // 勾选/取消勾选 回调函数
    handleSelectionChange: debounce(function(a) {
      this.$nextTick(() => {
        let total = this.handleCalculatePrice(this.renderDynamic)
        console.log('total', total)
        // this.remainingSum = total
        this.$emit('update:remainingSum', total)

        let selection = []
        this.renderDynamic.map(item => {
          //无子级
          if (item.isSelect == true && !item.children) {
            selection.push(item)
          }
          //有子级(全选)
          if (item.children && item.isSelect == true) {
            selection.push(item)
            selection.push(...item.children)
          }
          //有子级（不全选）
          if (item.children && item.isSelect === '') {
            selection.push(item)
            let cSelection = item.children.filter(cItem => cItem.isSelect == true)
            selection.push(...cSelection)
          }
        })
        this.$emit('update:selection', selection)
      })
    }, 300),
    //处理费用明细数据
    detailList(key, data) {
      console.log('key', key, 'data', data)
      if (['houseChargeItem', 'cashPledgeChargeItem', 'houseRefundItem', 'checkOutDelayRefundItem'].includes(key)) {
      }
      let listKey = ''
      switch (key) {
        case 'houseChargeItem':
          listKey = 'orderChargeItemList'
          data['fixedSelect'] = true
          data[listKey] = data[listKey].map((item, index) => {
            item['name'] = item.linkedOrderId ? '续住房费' : '房费'
            item['parentKey'] = key
            item['key'] = key + index
            item['fixedSelect'] = true
            return item
          })
          break
        case 'cashPledgeChargeItem':
          data['fixedSelect'] = true
          break
        case 'houseRefundItem':
          listKey = 'orderRefundDetailsList'
          data['fixedSelect'] = true
          data['itemSum'] = data.refundPrice
          data[listKey] = data[listKey].map((item, index) => {
            item['name'] = item.refundTime + '房费'
            item['parentKey'] = key
            item['key'] = key + index
            item['itemSum'] = item.refundPrice
            item['fixedSelect'] = true
            return item
          })
          break
        case 'facilityRefundItem':
          listKey = 'facilityDetailList'
          data['fixedSelect'] = true
          data[listKey] = data[listKey].map((item, index) => {
            item['parentKey'] = key
            item['key'] = key + index
            item['itemSum'] = item.price
            item['fixedSelect'] = true
            return item
          })
          break
        case 'unsubscribeRefundItem':
          listKey = 'orderRefundDetailsList'
          data['itemSum'] = data.refundPrice
          data[listKey] = data[listKey].map((item, index) => {
            item['name'] = item.refundTime.slice(5) + '退订费'
            item['parentKey'] = key
            item['key'] = key + index
            item['itemSum'] = item.refundPrice
            item['fixedSelect'] = false
            return item
          })
          if (data.itemSum === '0' || data.itemSum === 0) {
            data[listKey] = []
          }
          break
        case 'checkOutDelayRefundItem':
          data['fixedSelect'] = true
          break
        case'serviceCharge':
          data['fixedSelect'] = true
          break
        default:
          break
      }

      let disabled = this.isDetail ? true : false
      data['disabled'] = disabled
      if (data[listKey] && data[listKey].length > 0) {
        data[listKey].forEach((item, index) => {
          item['disabled'] = disabled
        })
      }

      if (listKey) {
        return {
          name: this.feeObj[key],
          key: key,
          id: key,
          ...data,
          children: listKey ? data[listKey] : null
        }
      } else {
        return {
          name: this.feeObj[key],
          key: key,
          id: key,
          ...data
        }
      }
    },
    //处理选中后价格计算
    handleCalculatePrice(row, totalPrice = 0) {
      // 'houseChargeItem''cashPledgeChargeItem'
      row.map(item => {
        if (item.isSelect === true) {
          totalPrice = ['houseChargeItem', 'cashPledgeChargeItem'].includes(item.key) ? totalPrice + item.itemSum : totalPrice - item.itemSum
        } else if (item.isSelect === '' && item.children) {
          item.children.forEach(sitem => {
            if (sitem.isSelect == true) {
              if (['houseChargeItem', 'cashPledgeChargeItem'].includes(sitem.parentkey)) {
                console.log('+')
                totalPrice = totalPrice + sitem.itemSum
              } else {
                console.log('-')
                totalPrice = totalPrice - sitem.itemSum
              }
            }

          })
        }
      })
      return totalPrice.toFixed(2)
    },
    expandChange(row) {
      row['isExpand'] = !row['isExpand']
    }
    ,
    //收起/展开 明细
    expand(row) {
      this.$refs.multipleTable.toggleRowExpansion(row)
    }
    ,
    //start
    // 复选框点击事件
    selectFun(selection, row) {
      if (this.isDetail) return
      console.log('selectFun')
      this.setRowIsSelect(row)
    }
    ,
    // 复选框点击事件
    setRowIsSelect(row) {
      //当点击父级点复选框时，当前的状态可能为未知状态，所以当前行状态设为false并选中，即可实现子级点全选效果
      console.log('row', row,'row.isSelect',row.isSelect)
      if (row.isSelect === '') {
        row.isSelect = false
        this.$refs.multipleTable.toggleRowSelection(row, true)
      }
      row.isSelect = !row.isSelect
      if (row.fixedSelect) {
        this.$refs.multipleTable.toggleRowSelection(row, true)
        row.isSelect = true
      }
      //
      if (row.isSelect == true) {
        this.$refs.multipleTable.toggleRowSelection(row, true)
      } else {
        this.$refs.multipleTable.toggleRowSelection(row, false)
      }
      //
      //是否经过外部渲染
      if (row.openRenderSelect) {
        if (row.renderSelect) {
          row.isSelect = true
          this.$refs.multipleTable.toggleRowSelection(row, true)
        } else {
          row.isSelect = false
          this.$refs.multipleTable.toggleRowSelection(row, false)
        }
      }

      let that = this

      function selectAllChildrens(data) {
        data.forEach((item) => {
          item.isSelect = row.isSelect
          that.$refs.multipleTable.toggleRowSelection(item, row.isSelect)
          if (item.children && item.children.length) {
            selectAllChildrens(item.children)
          }
        })

      }

      function getSelectStatus(selectStatuaArr, data) {
        data.forEach((childrenItem) => {
          selectStatuaArr.push(childrenItem.isSelect)
          if (childrenItem.children && childrenItem.children.length) {
            getSelectStatus(selectStatuaArr, childrenItem.children)
          }
        })
        return selectStatuaArr

      }

      function getLevelStatus(row) {
        //如果当前节点的parantId =0 并且有子节点，则为1
        //如果当前节点的parantId !=0 并且子节点没有子节点 则为3
        if (row.parentKey == 0) {
          if (row.children && row.children.length) {
            return 1
          } else {
            return 4
          }

        } else {

          if (!row.children || !row.children.length) {
            return 3
          } else {
            return 2
          }
        }
      }

      let result = {}

      //获取明确的节点
      function getExplicitNode(data, parentKey) {
        data.forEach((item) => {
          if (item.key == parentKey) {
            result = item
          }
          if (item.children && item.children.length) {
            getExplicitNode(item.children, parentKey)
          }
        })
        return result
      }

      function operateLastLeve(row) {
        //操作的是子节点  1、获取父节点  2、判断子节点选中个数，如果全部选中则父节点设为选中状态，如果都不选中，则为不选中状态，如果部分选择，则设为不明确状态
        let selectStatuaArr = []
        let item = getExplicitNode(that.renderDynamic, row.parentKey)
        selectStatuaArr = getSelectStatus(selectStatuaArr, item.children)
        if (
          selectStatuaArr.every((selectItem) => {
            return true == selectItem
          })
        ) {

          item.isSelect = true
          that.$refs.multipleTable.toggleRowSelection(item, true)
        } else if (
          selectStatuaArr.every((selectItem) => {
            return false == selectItem
          })

        ) {
          item.isSelect = false
          that.$refs.multipleTable.toggleRowSelection(item, false)
        } else {
          item.isSelect = ''
        }

        //则还有父级
        if (item.parentKey != 0) {
          operateLastLeve(item)
        }
      }

      //判断操作的是子级点复选框还是父级点复选框，如果是父级点，则控制子级点的全选和不全选
      //1、只是父级 2、既是子集，又是父级 3、只是子级
      let levelSataus = getLevelStatus(row)
      if (levelSataus == 1) {
        selectAllChildrens(row.children)
      } else if (levelSataus == 2) {
        selectAllChildrens(row.children)
        operateLastLeve(row)
      } else if (levelSataus == 3) {
        operateLastLeve(row)
      }
    }
    ,
    // 检测表格数据是否全选
    checkIsAllSelect() {
      this.oneProductIsSelect = []
      this.renderDynamic.forEach((item) => {
        this.oneProductIsSelect.push(item['isSelect'])
      })
      //判断一级产品是否是全选.如果一级产品全为true，则设置为取消全选，否则全选
      let isAllSelect = this.oneProductIsSelect.every((selectStatusItem) => {
        return true == selectStatusItem
      })
      return isAllSelect
    }
    ,
    // 表格全选事件
    selectAllFun(selection) {
      if (this.isDetail) return
      let isAllSelect = this.checkIsAllSelect()
      this.renderDynamic.forEach((item) => {
        item['isSelect'] = isAllSelect
        this.$refs.multipleTable.toggleRowSelection(item, !isAllSelect)
        this.selectFun(selection, item)
      })
    }
    ,
    // 表格行样式 当当前行的状态为不明确状态时，添加样式，使其复选框为不明确状态样式
    rowClassNameFun({ row }) {
      if (row.isSelect === '') {
        return 'indeterminate'
      }
    }
    ,
    // 表格标题样式 当一级目录有为不明确状态时，添加样式，使其全选复选框为不明确状态样式
    headerRowClassName({ row }) {
      let oneProductIsSelect = []
      this.renderDynamic.forEach((item) => {
        oneProductIsSelect.push(item.isSelect)
      })
      if (oneProductIsSelect.includes('')) {
        return 'indeterminate'
      }
      return ''

    }
    //end
  }
}
</script>

<style lang="scss" scoped>

</style>
<style lang="scss" scoped>
::v-deep .indeterminate .el-checkbox__input .el-checkbox__inner {
  background-color: #409eff !important;
  border-color: #409eff !important;
  color: #fff !important;
}

::v-deep .indeterminate .el-checkbox__input.is-checked .el-checkbox__inner::after {
  transform: scale(0.5);
}

::v-deep .indeterminate .el-checkbox__input .el-checkbox__inner {
  background-color: #f2f6fc;
  border-color: #dcdfe6;
}

::v-deep .indeterminate .el-checkbox__input .el-checkbox__inner::after {
  border-color: #c0c4cc !important;
  background-color: #c0c4cc;
}

::v-deep .product-show th .el-checkbox__inner {
  display: none !important;
}

::v-deep .indeterminate .el-checkbox__input .el-checkbox__inner::after {
  content: "";
  position: absolute;
  display: block;
  background-color: #fff;
  height: 2px;
  transform: scale(0.5);
  left: 0;
  right: 0;
  top: 5px;
  width: auto !important;
}

::v-deep .product-show .el-checkbox__inner {
  display: block !important;
}

::v-deep .product-show .el-checkbox {
  display: block !important;
}
</style>
